-- LUA环境安装
-- 下载地址：https://github.com/rjpcomputing/luaforwindows/releases

-- 控制台输出中文乱码问题解决方案:更改终端编码‌：在PowerShell或cmd中，可以通过执行`chcp 65001`命令将终端编码设置为UTF-8

-- 单行注释

--[[
多行注释
多行注释
多行注释
--]]

--[[
执行lua脚本：lua xxx.lua
全局变量：
    1.默认情况下，变量都是全局的
    2.变量不需要声明，赋值后即创建，未初始化的变量值为空：nil
    3.删除变量：将变量复制nil，即：varx = nil
数据类型（8个基本类型）：
    nil         :表示无效值，条件表达式中为false
    boolean     :false,true
    number      :双精度实浮点数，eg:1.123
    string      :字符串，eg:"strings",'strings'
    function    :C/Lua编写的函数
    userdata    :存储任意变量的C数据结构
    thread      :独立执行线路
    table       :关联数组
测试数据类型函数：type(xx)
--]]

-- lua的数据类型：
print("--- 基础类型测试 ---")
-- 空类型
print(type(nil))
-- 未定义(初始化)的变量其值为nil
print(type(xx))
print(type(('字符串：string')))
print(type(("字符串：string")))
-- 双精度浮点实数
print(type(123.321))
-- 布尔类型
print(type(true))
-- 关联数组
local tab01 = {
    k1 = "kkk1",
    k2 = "ppp2",
    k3 = 'zzz',
    k4 = 3.1415,
    k5 = true
}
print(type(tab01))
print(type(type({})))
-- 函数
local pp = print
print(type(pp))

-- if判断
local xx = nil
if xx == nil then
    print("xx is nil")
else
    if type(xx) == "nil" then
        print("type(xx) is \"nil\"")
    else
        print("type(xx) is not \"nil\"")
    end
end
-- 双精度实浮点数
print("--- 数字类型测试 ---")
print(type(1024))
print(type(1024.0))
print(type(1024.1024))
print(type(10e+2))
print(type(0.30e12))
print(type(3.1415 - 03))
print((1024))
print((1024.0))
print((1024.1024))
print((10e+2))
print((0.0031415e3))
print((314.15e-2))
-- 字符串定义
print("--- 字符串测试 ---")
local str1 = "PI=3.141592653A"
local str2 = 'PI=3.141592653B'
-- 换行的字符串
local str3 = [[
this is Block String
PI=3.141592653
PI=5857926
]]
print(str1)
print(str2)
print(str3)
local a = "3.14"
local b = 3.14
-- 字符串+ 尝试将字符串转为number
print(a + b)
-- 字符串连接使用【..】
print(a .. b)
-- 使用#计算字符串长度
print(#a)
print(#(a .. b))
print(#a .. b)

-- 数组
print("--- 数组测试 ---")
local myarray = {"Alice", 'Blice', 'Dlice'} -- 创建数组
print("数组长度:" .. #myarray)
-- 访问数组
for i = 1, #myarray do
    print("访问数组:" .. myarray[i])
end
for i, v in ipairs(myarray) do
    print("遍历输出数组", i, v)
end
print(myarray)
-- 添加数组元素 到数组末尾
myarray[#myarray+1] = "9527"
-- 删除数组末尾的元素
table.remove(myarray,#myarray)

-- 表格
print("--- 表格测试 ---")
local t = {} -- 定义表格
print(t)
t['name'] = 'Candy' -- 添加数据
t[9527] = 3.1415
t[9527] = 3.14166
print("访问表格数据：", t['name']) -- 访问数据
print("访问表格数据：", t[9527])
print("访问表格数据：", t[9528])
print("输出表格数据类型：", type(t[9527]))
print("输出表格数据类型：", type(t['name']))
print("输出表格数据类型：", type(t['nil']))
for k, v in pairs(t) do -- 遍历输出表格
    print("遍历输出表格", k, v)
end
print("-----")
for i, v in ipairs(t) do
    print("遍历输出表格", i, v)
end
print("表连接 ", table.concat(t))
-- 当我们获取 table 的长度的时候无论是使用 # 还是 table.getn 其都会在索引中断的地方停止计数，而导致无法正确取得 table 的长度
t = nil -- 删除表

-- 定义函数
print("--- 自定义函数 ---")
local function factorial1(n)
    if n == nil then
        return "n is nil"
    end
    if type(n) ~= type(1) then
        return "n is not the type of number"
    end
    if n <= 0 then
        return 1
    else
        return n * factorial1(n - 1)
    end
end

local xa = 10
print("Factoriall(5) is: " .. factorial1(5))
print("Factoriall(5) is: " .. factorial1(xa))
print("Factoriall(5) is: " .. factorial1('dff'))

print("--- 变量测试 ---")
-- 定义全局变量
local a = 55
-- 定义局部变量
local b = 66
local function joke()
    local c = 77
    local d = 88
end

joke()
d = nil
print(a, b, c, d)
do
    local a = 1055
    b = 1066
    print(a, b)
end
print(a, b)
a, b, c = 11055, 11066, 11077
print(a, b, c)
a, b, c = c, a, b
print(a, b, c)

-- 循环
print("--- 循环测试 ---")
function pp(n)
    return n + n
end

-- 标签
-- :label_x: print('--got label_x--')

-- for循环
step = 2
fstart = 10
fend = 16
for v = fstart, fend, step do
    if v % 3 == 0 then
        -- goto label_x
        break
    end
    print("Prime Number:" .. v)
end
-- wehile循环
a = 10
while (a > 0) do
    print("Reduce A : " .. a)
    a = a - 1
end
-- repeat循环
repeat
    print("Increace A : " .. a)
    a = a + 1
until (a > 10)
-- 函数
print("--- 函数测试 ---")
-- 普通自定义函数
function Values(obj)
    local k = {}
    for i=1 ,#obj do
        k[#k + 1] = (obj[i] + 77)
    end
    return k
end
local ret = Values({100, 200, 300, 400})
for i=1,#ret do
    print("Values :" .. ret[i])
end
-- 多返回值函数
local function myFunc(n)
    print("my local function")
    local a, b, c = 1024, 2048, 4096
    return a, b, c
end
r0,r1,r2 = myFunc(56) -- 函数的多返回值
print(r0)
print(r1)
print(r2)
-- 可变参数
print("--- 可变参数 ---")
function add(...)
    local s = 0
    for i, v in ipairs({...}) do
        if type(v) == type(0) then
            s = s + v
        end
    end
    print("Arg Count : " .. select("#", ...))
    print("Arg 5 is : " .. select(5, ...))
    return s
end

print("Add : " .. add(1, 2, 3, 4, "dff", {33}, false))
function add(title, ...)
    print(title .. "Arg Count : " .. select("#", ...))
    print("Arg 2 is : " .. select(2, ...))
end

add("LuaLua", 1, 1024, 2.56, 555)
-- 类型转换
print("--- 类型转换测试 ---")
local bV = false
local nV = 3.14
print("Boolean to string :" .. tostring(bV))
print("number to string :" .. tostring(nV))
local sv = "16"
local sv2 = "0xA"
print("string to number 10 :" .. tonumber(sv))
print("string to number 10 :" .. tonumber(sv, 16))
print("string to number 10 :" .. tonumber(sv2))
-- 运算符测试
print("--- 运算符测试 ---")
a = 7
b = 2
print("a = " .. a .. " b = " .. b)
print("a +  b =" .. a + b)
print("a -  b =" .. a - b)
print("a *  b =" .. a * b)
print("a /  b =" .. a / b)
-- print("a // b =" .. (a // b))
print("a ^  b =" .. a ^ b)
print("a %  b =" .. a % b)
print("  - a =" .. -a)
-- print("  ~ a =" .. ~a)
print("a == b " .. tostring(a == b))
print("a ~= b " .. tostring(a ~= b))
print("a >= b " .. tostring(a >= b))
print("a <= b " .. tostring(a <= b))
print("a > b " .. tostring(a > b))
print("a < b " .. tostring(a < b))
a = true
b = false
print("a = " .. tostring(a) .. " b = " .. tostring(b))
print("a & b = " .. tostring(a and b))
print("a | b = " .. tostring(a or b))
print("not a = " .. tostring(not a))
-- 字符串操作
print("--- 字符串操作 ---")
s = ">>>start_abc_DEF_123,4a56,78a9,'\"[,_end<<<"
print("Origin string is 【" .. s .. "】")
print("Upper : " .. string.upper(s))
print("Lower : " .. string.lower(s))
print("Replace : " .. string.gsub(s, "a", "x"))
print("Find : " .. string.find(s, "D"))
print("Reverse : " .. string.reverse(s))
print("Format :" .. string.format("this number is %d", 998))
print("Char to string :" .. string.char(99, 100, 101, 106))
print("Char to number :" .. string.byte('A'))
print("Char to number index :" .. string.byte('ABC', 2))
print("Length :" .. string.len(s))
print("Rep :" .. string.rep(s, 2))

print("--- 字符串的格式化 ---")
print("数字转换为ASCII字符 :%c " .. string.format("%c", 83))
print("数字转换为有符号整型:%d %i " .. string.format("%d %i", -8.3, -8.9))
print("数字转换为无符号整型:%u " .. string.format("%u", -8.5))
print("数字并将其转化为浮点数格式 %f " .. string.format("%f", 8.005))
print("数字并将其转化为科学记数法格式, 使用小写字母e %e " .. string.format("%e", 8.005))
print("数字并将其转化为科学记数法格式, 使用大写字母E %E " .. string.format("%E", 8.005))
print("数字并将其转化为%e(%E, 对应%G)及%f中较短的一种格式 %g %G " .. string.format("%g %G", 8.004, 8.005))
print("数字转换为八进制、小写十六进制、大写十六进制: %o %x %X " .. string.format("%o %x %X", 78, 78, 78))
print("字符串并将其转化为可安全被Lua编译器读入的格式 %q " .. string.format("%q", "ABCD"))
print("字符串并按照给定的参数格式化该字符串 %s " .. string.format("%s", "ABCD"))

print("字符与整型转换")
print(string.byte("lua"))
print(string.char(87))

print("--- 字符串模式匹配（类似正则表达式） ---")
print("用于匹配模式函数:string.find() string.gmatch() string.gsub() string.match()")
local str = "美国将自2025年8月1日起对所有巴西产品征收50%的关税"
local parttern = "%d%d%d%d"
ret,ret2,ret3 = string.find(str,parttern)
print(ret)
print(ret2)
print(ret3)
print(string.sub(str,ret,ret2))

print("---迭代器---")
-- 泛型for迭代器 ： 迭代函数（ipairs）、状态常量、控制变量
arrry = {"Line","Col","Space","UTF-8","CRLF"}
for k, v in ipairs(arrry) do
    print(k,v)
end
-- 无状态迭代器
function fac(iteratorMax,current)
    if current<iteratorMax then
        current = current + 1
        return current,(current-1)*1000
    end    
end
for i,v in fac,5,2 do
    print(i,v)
end
-- 多状态迭代器
function fac_status(collection)
    local index = 0
    local count = #collection
    return function ()
        index=index+1
        if index<=count 
        then
            return index*10,collection[index].."__K"
        end
    end    
end

for i,v in fac_status(arrry) do
    print(i,v)
end
print("模块与包")
-- 定义模块
mm={}
-- 在模块内定义一个常量
mm.varA =2025
-- 在模块内定义一个函数
function mm.add(a,b)
    return a+b
end
-- 模块内的私有函数
local function addx(a,b)
    return a+b
end

-- 加载模块
local mdb1 = require("lua_use_db")
local mdb2 = require "lua_use_db"
-- 模块加载机制：

